package com.wolf.create;

import java.awt.Component;
import java.awt.Container;
import java.awt.GridLayout;
import java.awt.List;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.ItemEvent;
import java.awt.event.ItemListener;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
import java.util.Properties;
import java.util.Vector;

import javax.swing.*;
import javax.swing.border.TitledBorder;
import javax.swing.table.DefaultTableModel;

import org.apache.commons.lang3.StringUtils;

import com.wolf.create.method.CreateMethod;
import com.wolf.create.method.DataDeal;
import com.wolf.create.model.ConnectModel;
import com.wolf.create.model.DataModel;
import com.wolf.create.model.JtableDataModel;
import com.wolf.create.utils.DBSqlDeal;
import org.apache.log4j.Logger;

public class ProjectMain extends JFrame {

	public static Logger log = Logger.getLogger(ProjectMain.class);

	private static final long serialVersionUID = 1L;

	private JButton jb = new JButton();
	private JComboBox<?> dataType;
	private JTextField dataAddr, dataName, dataPort, dataUserName, dataUserPWD;

	private JComboBox<String> tableSelect;
	JCheckBox createModel, createController, createService, createServiceImpl;
	JCheckBox createMapper, createMapping;
	JCheckBox createLookPage, createMessagePage, createEditPage;

	JTable tableList;
	private JFrame jframe = new JFrame("文件生成工具");

	private String pojoPackageName;

	private JComboBox<String> configSelect;
	JCheckBox swagger, lombok;

	private Map<String,String> tableMap=new HashMap<String,String>();
	public ProjectMain(Class<?> class1) {
		pojoPackageName = class1.getPackage().getName();
		// 创建主容器
		jframe.setLayout(null);
		Container c = jframe.getContentPane();

		// 创建输入面板
		JPanel dbMessage = new JPanel();
		TitledBorder dbTitle = new TitledBorder("数据库信息");
		dbMessage.setBorder(dbTitle);
		dbMessage.setLayout(new GridLayout(3, 5));
		dbMessage.setBounds(20, 8, 840, 80);

		JLabel dataTypeLabel = new JLabel("数据库类型:   ");
		dataTypeLabel.setHorizontalAlignment(SwingConstants.RIGHT);
		String dataTypeSelect[] = { "Mssql", "Mysql", "oracle" };
		dataType = new JComboBox<Object>(dataTypeSelect);
		dataType.addItemListener(new ItemListener() {
			public void itemStateChanged(final ItemEvent e) {
				String dataTypeValue = dataType.getSelectedItem().toString();
				if (dataTypeValue.equalsIgnoreCase("Mssql")) {
					dataPort.setText("1433");
				} else if (dataTypeValue.equalsIgnoreCase("mysql")) {
					dataPort.setText("3306");
				} else {
					dataPort.setText("1521");
				}
			}
		});
		dataType.addActionListener(new ActionListener() {
			public void actionPerformed(final ActionEvent e) {
				String dataTypeValue = dataType.getSelectedItem().toString();
				if (dataTypeValue.equalsIgnoreCase("Mssql")) {
					dataPort.setText("1433");
					dataUserName.setText("sa");
					dataUserPWD.setText("");
				} else if (dataTypeValue.equalsIgnoreCase("mysql")) {
					dataPort.setText("3306");
					dataUserName.setText("root");
					dataUserPWD.setText("");
				} else {
					dataPort.setText("1521");
					dataUserName.setText("sys");
					dataUserPWD.setText("change_on_install");
				}
			}
		});
		dbMessage.add(dataTypeLabel);
		dbMessage.add(dataType);

		JLabel dataAddrLabel = new JLabel("数据库地址:   ");
		dataAddrLabel.setHorizontalAlignment(SwingConstants.RIGHT);
		dataAddr = new JTextField("127.0.0.1");
		dataAddr.setSize(90, 24);
		dbMessage.add(dataAddrLabel);
		dbMessage.add(dataAddr);

		// 从文件中读取配置信息
		JButton readProperties = new JButton("从文件中读取配置");
		readProperties.setSize(90, 24);
		dbMessage.add(readProperties);
		readProperties.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				getDBFromProperties();
			}
		});

		JLabel dataPortLabel = new JLabel("数据库端口号:   ");
		dataPortLabel.setHorizontalAlignment(SwingConstants.RIGHT);
		dataPort = new JTextField("1433");
		dataPort.setSize(100, 10);
		// 过滤输入的字符,只能填数字
		dataPort.addKeyListener(new java.awt.event.KeyAdapter() {
			public void keyReleased(java.awt.event.KeyEvent e) {
				// 首先得获取到键盘按下的字符
				// 然后进行判断是否是数字键，如果不是，则取消这次操作
				// public void consume()使用此事件，以便不会按照默认的方式由产生此事件的源代码来处理此事件。
				char c = e.getKeyChar();
				if (!(c >= '0' && c <= '9')) {
					String dataTypeValue = dataType.getSelectedItem().toString();
					if (dataTypeValue.equalsIgnoreCase("Mssql")) {
						dataPort.setText("1433");
					} else if (dataTypeValue.equalsIgnoreCase("mysql")) {
						dataPort.setText("3306");
					} else {
						dataPort.setText("1521");
					}
				}
			}
		});
		dbMessage.add(dataPortLabel);
		dbMessage.add(dataPort);

		JLabel dataNameLabel = new JLabel("数据库名称:   ");
		dataNameLabel.setHorizontalAlignment(SwingConstants.RIGHT);
		dataName = new JTextField("PAC");
		dataName.setSize(90, 24);
		dbMessage.add(dataNameLabel);
		dbMessage.add(dataName);
		// pSex1 = new JRadioButton("男", true);
		// pSex1.setSize(100, 10);
		// pSex2 = new JRadioButton("女");
		// pSex2.setSize(100, 10);
		// group = new ButtonGroup();
		// group.add(pSex1);
		// group.add(pSex2);
		// JPanel jpSex = new JPanel();
		// jpSex.setBounds(0, 0, 100, 20);
		// jpSex.add(pSex1);
		// jpSex.add(pSex2);
		// 预留按钮1
		JButton extend1 = new JButton("预留按钮1");
		extend1.setSize(70, 24);
		dbMessage.add(extend1);

		JLabel userNameLabel = new JLabel("用户名:   ");
		userNameLabel.setHorizontalAlignment(SwingConstants.RIGHT);
		dataUserName = new JTextField("sa");
		dbMessage.add(userNameLabel);
		dbMessage.add(dataUserName);

		JLabel userPWDLabel = new JLabel("密码:   ");
		userPWDLabel.setHorizontalAlignment(SwingConstants.RIGHT);
		dataUserPWD = new JTextField("");
		dbMessage.add(userPWDLabel);
		dbMessage.add(dataUserPWD);

		c.add(dbMessage);

		// 创建输入面板
		JPanel tableMessage = new JPanel();
		TitledBorder centertitle = new TitledBorder("表信息");
		tableMessage.setBorder(centertitle);
		tableMessage.setLayout(null);
		tableMessage.setBounds(20, 100, 840, 280);

		tableSelect = new JComboBox<String>();
		tableSelect.setBounds(80, 18, 280, 20);

		JButton getTables = new JButton("获取表对象");
		getTables.setHorizontalAlignment(SwingConstants.RIGHT);
		getTables.setBounds(380, 18, 100, 20);
		getTables.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				getTables();
			}
		});

		JButton getTablesColumn = new JButton("加载列信息");
		getTablesColumn.setHorizontalAlignment(SwingConstants.RIGHT);
		getTablesColumn.setBounds(500, 18, 100, 20);
		getTablesColumn.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				getTablesColumn();
			}
		});

		tableMessage.add(tableSelect);
		tableMessage.add(getTables);
		tableMessage.add(getTablesColumn);

		String[] columnNames = { "字段序号", "字段名", "字段类型", "索引", "主键", "字段长度", "允许空", "默认值", "备注", "查询方式", "其它操作" };
		// Object[][] data = new Object[2][8];
		DefaultTableModel tableModel = new DefaultTableModel(null, columnNames);

		tableList = new JTable(tableModel);
		// table = new JTable(new MyTableModel());
		tableList.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);// 设置单选
		tableList.setAutoResizeMode(JTable.AUTO_RESIZE_OFF);// 关闭表格自动调整

		// table.s
		/* 用JScrollPane装载JTable，这样超出范围的列就可以通过滚动条来查看 */
		JScrollPane scroll = new JScrollPane(tableList);
		scroll.setBounds(10, 50, 820, 220);
		tableMessage.add(scroll);
		c.add(tableMessage);

		// 创建输入面板
		JPanel configPanel = new JPanel();
		TitledBorder configTitle = new TitledBorder("文件配置选项");
		configPanel.setBorder(configTitle);
		configPanel.setLayout(new GridLayout(3, 3));
		configPanel.setBounds(20, 400, 840, 120);

		JRadioButton randioButton1=new JRadioButton("Java");
		JRadioButton randioButton2=new JRadioButton("PHP",true);
		JRadioButton randioButton3=new JRadioButton("C++");
		configPanel.add(randioButton1);
		configPanel.add(randioButton2);
		configPanel.add(randioButton3);

		ButtonGroup swaggerGroup=new ButtonGroup();
		swaggerGroup.add(randioButton1);
		swaggerGroup.add(randioButton2);
		swaggerGroup.add(randioButton3);

		c.add(configPanel);


		// 创建文件选项面板
		JPanel underPanel = new JPanel();
		TitledBorder undertitle = new TitledBorder("生成文件选项");
		underPanel.setBorder(undertitle);
		underPanel.setLayout(null);
		underPanel.setBounds(20, 600, 840, 120);

		JPanel createSelect = new JPanel();
		createSelect.setLayout(new GridLayout(3, 3));
		createSelect.setBounds(20, 20, 700, 90);

		createModel = new JCheckBox("生成 Model");
		createModel.setName("Model");
		createModel.setSelected(true);

		createController = new JCheckBox("生成 Controller");
		createController.setName("Controller");
		createController.setSelected(true);

		createService = new JCheckBox("生成 Service");
		createService.setName("Service");
		createService.setSelected(true);

		createServiceImpl = new JCheckBox("生成 ServiceImpl");
		createServiceImpl.setName("ServiceImpl");
		createServiceImpl.setSelected(true);

		createMapper = new JCheckBox("生成 Mapper");
		createMapper.setName("Mapper");
		createMapper.setSelected(true);

		createMapping = new JCheckBox("生成 Mapping");
		createMapping.setName("Mapping");
		createMapping.setSelected(true);

		createLookPage = new JCheckBox("生成 ListPage");
		createLookPage.setName("ListPage");
		createLookPage.setSelected(true);

		createMessagePage = new JCheckBox("生成 MessagePage");
		createMessagePage.setName("MessagePage");
		createMessagePage.setSelected(true);

		createEditPage = new JCheckBox("生成 EditPage");
		createEditPage.setName("EditPage");
		createEditPage.setSelected(true);

		createSelect.add(createModel);
		createSelect.add(createController);
		createSelect.add(createService);
		createSelect.add(createServiceImpl);
		createSelect.add(createMapper);
		createSelect.add(createMapping);
		createSelect.add(createLookPage);
		createSelect.add(createMessagePage);
		createSelect.add(createEditPage);

		JButton checkAll = new JButton();
		checkAll.setText("全选");
		checkAll.setBounds(720, 20, 60, 26);
		final Component[] components = createSelect.getComponents();
		checkAll.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				doSelect(components);
			}
		});

		JButton checkReverse = new JButton();
		checkReverse.setText("反选");
		checkReverse.setBounds(720, 50, 60, 26);
		checkReverse.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				doUnSelect(components);
			}
		});

		jb.setText("确定");
		jb.setBounds(720, 80, 60, 26);
		jb.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				createPojo(components);
			}
		});

		underPanel.add(checkAll);
		underPanel.add(checkReverse);
		underPanel.add(jb);
		underPanel.add(createSelect);
		c.add(underPanel);

		// 显示窗体
		jframe.setVisible(true);
		// 设置窗体大小
		jframe.setSize(1200, 900);
		// 居中显示
		jframe.setLocationRelativeTo(null);

		jframe.addWindowListener(new WindowAdapter() {
			public void windowClosing(WindowEvent e) {
				exit();
			}
		});

	}

	// 从文件中加载数据库配置信息
	private void getDBFromProperties() {
		log.info("从文件中加载数据库配置信息");
		InputStream inStream = ClassLoader.getSystemResourceAsStream("autoCreateConfig.properties");
		Properties prop = new Properties();
		try {
			prop.load(inStream);
		} catch (IOException e) {
			System.out.println("未在resources目录中读取到autoCreateConfig.properties配置文件");
			e.printStackTrace();
		}
		dataType.setSelectedItem(prop.getProperty("dataType"));
		dataAddr.setText(prop.getProperty("dataAddr"));
		dataName.setText(prop.getProperty("dataName"));
		dataPort.setText(prop.getProperty("dataPort"));
		dataUserName.setText(prop.getProperty("dataUserName"));
		dataUserPWD.setText(prop.getProperty("dataUserPWD"));
		try {
			prop.clear();
			prop.clone();
			inStream.close();
		} catch (IOException e) {
			e.printStackTrace();
		}
	}

	// 加载表
	private void getTables() {
		ConnectModel connectModel = getConnectModel();
		ArrayList<Object> dbTables = DBSqlDeal.executeSql(connectModel.getTableQuerySql(), connectModel);
		tableSelect.removeAllItems();
		tableMap.clear();
		if (dbTables.size() > 0) {
			for (int i = 0; i < dbTables.size(); i++) {
				Object[] objects = (Object[]) dbTables.get(i);
				tableSelect.addItem(objects[0].toString()+" : "+objects[1].toString());
				tableMap.put(objects[0].toString(),objects[1].toString());
			}
		}
//		list.forEach((k,v)->{
//			System.out.println(k+":"+v);
//		});
	}

	// 加载列信息
	private void getTablesColumn() {
		ConnectModel connectModel = getConnectModel();
		// 获取执行结果
		ArrayList<Object> dbTables = DBSqlDeal.executeSql(connectModel.getColumnQuerySql(), connectModel);
		DefaultTableModel tableModel = (DefaultTableModel) tableList.getModel();
		tableModel.setRowCount(0);// 清除原有行
		if (dbTables.size() > 0) {
			for (int i = 0; i < dbTables.size(); i++) {
				Object[] objects = (Object[]) dbTables.get(i);
				tableModel.addRow(objects);
			}
		}
		final JComboBox<String> searchWay = new JComboBox<String>();
		searchWay.addItem("=");
		searchWay.addItem(">");
		searchWay.addItem("<");
		searchWay.addItem("<>");
		searchWay.addItem("like");
		// searchWay.setEditable(true);
		tableList.getColumnModel().getColumn(9).setCellEditor(new DefaultCellEditor(searchWay));

		final JComboBox<String> otherOper = new JComboBox<String>();
		otherOper.addItem("and");
		otherOper.addItem("or");
		tableList.getColumnModel().getColumn(10).setCellEditor(new DefaultCellEditor(otherOper));
		// 更新表格
		tableList.updateUI();
		tableList.invalidate();
		// System.out.println(tableModel);
		// 填充数据
		/*
		 * for(Member member:members){ String[] arr=new String[3];
		 * arr[0]=member.getName(); arr[1]=member.getAge();
		 * arr[2]=member.getTitle();
		 * 
		 * // 添加数据到表格 tableModel.addRow(arr); }
		 */
	}

	// 全选
	public void doSelect(Component[] components) {
		for (Component component : components) {
			if (component instanceof JCheckBox) {
				((JCheckBox) component).setSelected(true);
			}
		}
	}

	// 反选
	public void doUnSelect(Component[] components) {
		for (Component component : components) {
			if (component instanceof JCheckBox) {
				((JCheckBox) component).setSelected(false);
			}
		}
	}

	// 退出
	public void exit() {
		Object[] options = { "确定", "取消" };
		JOptionPane pane2 = new JOptionPane("确定退出吗?", JOptionPane.QUESTION_MESSAGE, JOptionPane.YES_NO_OPTION, null,
				options, options[1]);
		JDialog dialog = pane2.createDialog(this, "警告");
		dialog.setVisible(true);
		Object selectedValue = pane2.getValue();
		if (selectedValue == null || selectedValue == options[1]) {
			jframe.setDefaultCloseOperation(JFrame.DO_NOTHING_ON_CLOSE); // 这个是关键
		} else if (selectedValue == options[0]) {
			jframe.setDefaultCloseOperation(EXIT_ON_CLOSE);
		}
	}

	// 确定生成文件
	public void createPojo(Component[] components) {
		// 获取选择的生成文件选项
		ArrayList<String> createSelect = new ArrayList<String>();
		for (Component component : components) {
			if (component instanceof JCheckBox) {
				// ((JCheckBox) component).setSelected(false);
				if (((JCheckBox) component).isSelected())
					createSelect.add(((JCheckBox) component).getName().trim());
			}
		}

		DefaultTableModel tableModel = (DefaultTableModel) tableList.getModel();
		Vector<?> rowData = tableModel.getDataVector();
		ArrayList<JtableDataModel> jtableDataModels = new ArrayList<JtableDataModel>();
		for (int i = 0, n = rowData.size(); i < n; i++) {
			String rowString = new String(rowData.get(i).toString());
			String[] row = rowString.substring(1, rowString.length() - 1).split(",");
			JtableDataModel jtableDataModel = new JtableDataModel();
			if (row[0] != null && !row[0].equalsIgnoreCase("null"))
				jtableDataModel.setNum(Integer.parseInt(row[0].trim()));
			jtableDataModel.setDbColumnName(row[1].trim().toLowerCase());
			jtableDataModel.setDbColumnType(row[2].trim());
			if (row[3].trim().equalsIgnoreCase("index") || row[3].trim().equalsIgnoreCase("yes"))
				jtableDataModel.setIndexKey(true);
			if (row[4].trim().equalsIgnoreCase("PRI") || row[4].trim().equalsIgnoreCase("yes"))
				jtableDataModel.setPrimayKey(true);
			if (row[5].trim() != null && !row[5].trim().equalsIgnoreCase("null")) {
				jtableDataModel.setColumnLength(Integer.parseInt(row[5].trim()));
			}
			if (row[6].trim().equalsIgnoreCase("yes"))
				jtableDataModel.setNullValue(true);
			if (row[7].trim() != null)
				jtableDataModel.setDefaultValue(row[7].trim());
			jtableDataModel.setComment(row[8].trim());
			jtableDataModel.setSearchWay(row[9].trim());
			jtableDataModel.setOtherOper(row[10].trim());
			jtableDataModels.add(jtableDataModel);
			row = null;
		}
		DataModel dm = new DataModel();
		//从文件中获包名or获取所在包路径
		String configPojoPackageName=getTextFromProperties("pojoPackageName");
		if(StringUtils.isNoneBlank(configPojoPackageName)) {
			dm.setEntityPackageName(pojoPackageName);
		}else {
			dm.setEntityPackageName(configPojoPackageName);
		}
		
		dm.setTableName(getConnectModel().getTableName());
		rowData = null;
		dm.setArrayList(jtableDataModels);

//		dm = DataDeal.JtableToData(dm);
//		CreateMethod method = new CreateMethod(dm);
//
//		method.execMethod(createSelect);
//		System.out.println(dm.toString());

		/*
		 * Patient p=new Patient(); p.setName(userName.getText());
		 * p.setHeight(pHeight.getText()); p.setWeight(pWeight.getText());
		 * p.setType(type.getText());
		 * p.setSex(pSex1.isSelected()?pSex1.getText():pSex2.getText());
		 * p.setDet(detail.getText()); JOptionPane.showMessageDialog(null,
		 * p.toString());
		 */

	}

	/**
	 * @Title: ConnectModel
	 * @Description: 设置链接数据库属性
	 * @return ConnectModel
	 */
	public ConnectModel getConnectModel() {
		ConnectModel connectModel = new ConnectModel();
		String dbType = dataType.getSelectedItem().toString();
		connectModel.setDbType(dbType);
		connectModel.setDbAddr(dataAddr.getText());
		connectModel.setDbPort(dataPort.getText());
		connectModel.setDbName(dataName.getText());
		connectModel.setDbUserName(dataUserName.getText());
		connectModel.setDbUserPWD(dataUserPWD.getText());

		if (tableSelect.getSelectedItem() != null && !tableSelect.getSelectedItem().equals("")) {
			String table = tableSelect.getSelectedItem().toString().split(":")[0].trim();
			connectModel.setTableName(table);
		}

		return connectModel;
	}

	/*
	 * public static void main(String[] args) { new ProjectMain(); }
	 */

	// 创建行标题栏，左侧不可移动，右侧可动
	// public class MfixedColumnTable extends JPanel {
	// protected Vector<String> columnNameV; // 固定列名数组
	// protected Vector<Vector<Object>> tableValueV; // 表格数据数组
	// protected int fixedColumn = 1;// 固定列数量
	// protected JTable fixedColumnTable; //固定表格对象
	// private FixedColumnTableModel fixedColumnTableModel; //固定列表表格模型对象
	// protected JTable floatingColumnTable; //移动列表格对象
	// private FloatingColumnTableModel floatingColumnTableModel;
	// }
	//
	// private class MListSelectionListener implements ListSelectionListener {
	// boolean isFixedColumnTable = true; //默认由选中列表格中的行触发
	//
	//
	// public MListSelectionListener(boolean isFixedColumnTable){
	// this.isFixedColumnTable = isFixedColumnTable;
	// }
	// @Override
	// public void valueChanged(ListSelectionEvent e) {
	// if(isFixedColumnTable){
	// /*int row = fixedColumnTable.getSelectedRow();
	// floatingColumnTable.setRowSelectionInteval(row,row);
	// */}else{
	// /*int row = floatingColumnTable.getSelectedRow();
	// fixedColumnTable.setRowSelectionInteval(row,row);
	// */}
	// }
	//
	// }
	// private class FixedColumnTableModel extends MfixedColumnTable{
	// //AbstractTableModel {
	// public int getColumnCount() {
	// return fixedColumn;
	// }
	//
	// public int getRowCount() {
	// return tableValueV.size();
	// }
	//
	// // 返回指定单元格的值
	// public Object getValueAt(int rowIndex, int columnIndex) {
	// return tableValueV.get(rowIndex).get(columnIndex);
	// }
	//
	// public String getColumnName(int columnIndex) {
	// return columnNameV.get(columnIndex); // 返回指定列的名称
	// }
	// }
	//
	// private class FloatingColumnTableModel extends MfixedColumnTable {
	// public int getColumnCount() { // 返回可移动列的数量
	// return columnNameV.size() - fixedColumn;// 需要扣除固定列的数量
	// }
	//
	// public int getRowCount() {
	// return tableValueV.size(); // 返回行数
	// }
	//
	// //返回指定单元格的值
	// public Object getValueAt(int rowIndex, int columnIndex) {
	// return tableValueV.get(rowIndex).get(columnIndex + fixedColumn);
	// }
	// public String getColumnName(int columnIndex){
	// return columnNameV.get(columnIndex+fixedColumn);
	// }
	// }
	
	// 从文件中加载数据库配置信息
	private String getTextFromProperties(String propertiesName) {
			InputStream inStream = ClassLoader.getSystemResourceAsStream("autoCreateConfig.properties");
			Properties prop = new Properties();
			try {
				prop.load(inStream);
			} catch (IOException e) {
				System.out.println("未在resources目录中读取到autoCreateConfig.properties配置文件");
				e.printStackTrace();
			}
			String value=prop.getProperty(propertiesName);
			try {
				prop.clear();
				prop.clone();
				inStream.close();
			} catch (IOException e) {
				e.printStackTrace();
			}
			return value;
		}
}